package com.qf.service.impl;

import com.qf.cache.DefaultRoleCache;
import com.qf.cache.RoleCache;
import com.qf.events.AddUserEvent;
import com.qf.events.UserLoginEvent;
import com.qf.exeptions.AddDataException;
import com.qf.exeptions.QueryDataException;
import com.qf.exeptions.ResultCode;
import com.qf.mappers.UserMapper;
import com.qf.pojo.*;
import com.qf.service.UserService;
import com.qf.utils.MD5Utils;
import com.qf.utils.SecurityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
import org.springframework.util.StringUtils;

import java.util.Date;
import java.util.List;

/*
杨威
2021/12/29
23:05
*/
@Service
@Transactional//事务管理
public class UserServiceImpl implements UserService {
    @Autowired
    UserMapper userMapper;
    @Autowired
    DefaultRoleCache defaultRoleCache;
    @Autowired
    RoleCache roleCache;
    @Autowired
    ApplicationContext ac;
    public void addUser(User user) {

        //1判断传递的数据是否完整
        Assert.isTrue(!user.isEmpty(CheckType.ADD), () -> {
            throw new AddDataException("必须传递的数据不完整,请检查", ResultCode.USERDATA_NULL);
        });
        //2查询用户是否已经存在
        List<User> userList = userMapper.selectByUserNameOrPhoneOrEmail(user.getUsername(), user.getPhone(), user.getEmail());

        //断言集合的长度是0 否则就抛异常
        Assert.isTrue(userList.size()==0,()->{
            throw new AddDataException("用户已经存在",ResultCode.DATA_ALREADY_EXIST);
        });

        //对密码进行加密处理
        String password = user.getPassword();
        String salt = MD5Utils.getRandomString(15);//生成了一个长度15的盐
        String md5 = MD5Utils.getMd5(password, salt, 1024);
        user.setPassword(md5);
        user.setPwdSalt(salt);
        user.setCreateTime(new Date());
        user.setCreateBy(user.getUsername());
//直接查询数据库 不能适应高并发场景
//        Long roleId = defaultRoleMapper.selectRoleIdByType("user");
//        Role role = roleMapper.selectById(roleId);
        DefaultRole defaultRole = defaultRoleCache.getValue("user");
        Role role = roleCache.getValue(defaultRole.getRoleId());
        SecurityUtils.getRequest().getSession().setAttribute("role",role);
        user.setRemark(role.getRemark());
        userMapper.addUser(user);
        System.out.println("user = " + user);
        SecurityUtils.getRequest().getSession().setAttribute("user",user);
        ac.publishEvent(new AddUserEvent());
    }

    public User login(String username,String password){
        //判断传递的数据不能为空
        Assert.isTrue(StringUtils.hasText(username)&&StringUtils.hasText(password),()->{
            throw new QueryDataException("用户名或密码错误",ResultCode.USERNAME_PASSOERD_ERROR);
        });
        //查询用户名在数据库是否存在
        User user = userMapper.selectByUserName(username);
        Assert.notNull(user,()->{
            throw new QueryDataException("用户名或密码错误",ResultCode.USERNAME_PASSOERD_ERROR);
        });
        //判断密码是否正确
        String md5 = MD5Utils.getMd5(password, user.getPwdSalt(), 1024);
        Assert.isTrue(md5.equals(user.getPassword()),()->{
            throw new QueryDataException("用户名或密码错误",ResultCode.USERNAME_PASSOERD_ERROR);
        });
        user.setPassword(null);
        user.setPwdSalt(null);

        //说明用户传递的用户名和密码是正确的
        return user;
    }

    public void updateUserLogin(User user){
        userMapper.upDateUserLogin(user);
    }

    @Override
    public User findUserByUserName(String username) {
        Assert.notNull(username,()->{
            throw new QueryDataException("用户名不能为空",ResultCode.DATA_EMPTY);
        });
        return userMapper.selectByUserName(username);
    }
}
